package com.xenione.libs.swipemaker.orientation;

import com.xenione.libs.swipemaker.Anchors;
import com.xenione.libs.swipemaker.Position;
import com.xenione.libs.swipemaker.ScrollerHelper;
import com.xenione.libs.swipemaker.SwipeLayout;
import com.xenione.libs.swipemaker.SwipeTouchListener;
import ohos.agp.animation.Animator;
import ohos.agp.animation.AnimatorValue;
import ohos.agp.components.Component;
import ohos.agp.components.ComponentParent;
import ohos.app.Context;
import ohos.multimodalinput.event.TouchEvent;

/**
 * Created by Eugeni on 28/09/2016.
 */
public abstract class OrientationStrategy {

    private Position mPositionInfo;
    private SwipeLayout.OnTranslateChangeListener mOnTranslateChangeListener;
    public int mTouchSlop;
    private AnimatorValue mAnimatorValue;
    private float from;
    private float to;
    public boolean isCheckTouch = false;
    private SwipeTouchListener mSwipeTouchListener;

    public void setSwipeTouchListener(SwipeTouchListener swipeTouchListener) {
        mSwipeTouchListener = swipeTouchListener;
    }

    public void setTouchSlop(int touchSlop) {
        this.mTouchSlop = touchSlop;
    }

    public OrientationStrategy(Component view) {
        this(view, view.getTag() == null ? 0 : Integer.parseInt(view.getTag().toString()));
        System.out.println("----- tag = " + view);
    }

    public OrientationStrategy(Component view, int touchSlop) {
        mTouchSlop = touchSlop;
        mPositionInfo = new Position();
        mAnimatorValue = new AnimatorValue();
    }

    public void setAnchor(Integer... points) {
        mPositionInfo.setAnchors(Anchors.make(points));
    }

    public void setOnTranslateChangeListener(SwipeLayout.OnTranslateChangeListener listener) {
        mOnTranslateChangeListener = listener;
    }

    public abstract boolean onTouchEvent(TouchEvent e);

    abstract int getDelta();

    abstract void setDelta(int delta);

    public void translateBy(int delta){
        translateTo(getDelta() + delta);
    }

    public void translateTo(int distance) {
        int cropped = ensureInsideBounds(distance);
        if (getDelta() == cropped) {
            return;
        }
        setDelta(cropped);
        updatePosition(cropped);
    }

    private void updatePosition(int newPosition) {
        mPositionInfo.updatePosition(newPosition);
        notifyListener();
    }
    private void notifyListener() {
        if (mOnTranslateChangeListener != null) {
            mOnTranslateChangeListener.onTranslateChange(mPositionInfo.global, mPositionInfo.section, mPositionInfo.relative);
        }

       // Log.i("translate", "global x: " + mPositionInfo.global + " section:" + mPositionInfo.section + " relative:" + mPositionInfo.relative);
    }

    private int ensureInsideBounds(int x) {
        return mPositionInfo.cropInLimits(x);
    }

    boolean fling() {
        int start = getDelta();
        int end = endPositionFrom(start);
        System.out.println("----- start = " + start +" end = " +end);
        from = start;
        to = end;
        mAnimatorValue.setDuration(100);
        mAnimatorValue.setValueUpdateListener(new AnimatorValue.ValueUpdateListener() {
            @Override
            public void onUpdate(AnimatorValue animatorValue, float v) {

                if(v == 1) {
                    return;
                }
                translateTo((int) (from + v * (to - from)));
            }
        });

        mAnimatorValue.setStateChangedListener(new Animator.StateChangedListener() {
            @Override
            public void onStart(Animator animator) {

            }

            @Override
            public void onStop(Animator animator) {

            }

            @Override
            public void onCancel(Animator animator) {

            }

            @Override
            public void onEnd(Animator animator) {
                translateTo((int) to);
            }

            @Override
            public void onPause(Animator animator) {

            }

            @Override
            public void onResume(Animator animator) {

            }
        });
        mAnimatorValue.start();
        return true;
    }

    private int endPositionFrom(int currPosition) {
        return mPositionInfo.closeTo(currPosition);
    }

    void disallowParentInterceptTouchEvent(boolean disallow) {
        System.out.println("-------- mSwipeTouchListener = " + mSwipeTouchListener);
        if (mSwipeTouchListener != null) {
            mSwipeTouchListener.requestDisallowInterceptTouchEvent(disallow);
        }
    }

    public void startWith(int position) {
        mPositionInfo.setCurrPos(position);
    }
}
